#include "stdafx.h"
#include "HookSettingReader.h"
#include "ExceptionList.h"


HookSettingReader::HookSettingReader(PWSTR pszHookSettingFilePath): m_pHookEngine( new HookEngine() )
{
	assert( pszHookSettingFilePath!=NULL );
	assert( !IsBadStringPtrW(pszHookSettingFilePath, MAX_PATH) );

	if( pszHookSettingFilePath==NULL )
	{
		ArgumentException aeobj("The parameter 'pszHookSettingFilePath' is NULL\n");
		throw aeobj;
	}

	if( IsBadStringPtrW(pszHookSettingFilePath, MAX_PATH) )
	{
		ArgumentException aeobj("The parameter 'pszHookSettingFilePath' is a bad string\n");
		throw aeobj;
	}

	errno_t errReturn = wcscpy_s( m_szHookSettingFilePath, MAX_PATH, pszHookSettingFilePath);
	assert( errReturn==0 );

	BOOL fReadResult = Read();
	assert( fReadResult );
}

BOOL HookSettingReader::Read()
{
	ifstream settingFile(m_szHookSettingFilePath, ios_base::in|ios_base::binary);
	assert( settingFile!=NULL );
	if( settingFile==NULL)
	{
		TRACE(TEXT("The file path %s is incorrect\n"), m_szHookSettingFilePath);
		return FALSE;
	}

	settingFile.read((char *)&(this->m_dwHookSettingEntryCount), sizeof(m_dwHookSettingEntryCount));
	bool fResult = settingFile.fail();
	assert(!fResult);
	if(fResult)
	{
		TRACE(TEXT("Reading m_dwHookSettingEntryCount failed\n"));
		return FALSE;
	}

	assert( m_dwHookSettingEntryCount<= MaxHookSettingEntryCount );
	if(m_dwHookSettingEntryCount>MaxHookSettingEntryCount)
	{
		TRACE(TEXT("Corrupted log file\n"));
		return FALSE;
	}

	settingFile._Read_s( 
		(char *)(this->m_HookSettingEntryArray), 
		m_dwHookSettingEntryCount*sizeof(HookSettingEntry),
		m_dwHookSettingEntryCount*sizeof(HookSettingEntry)
		);
	fResult = settingFile.fail();
	assert(!fResult);
	if(fResult)
	{
		TRACE(TEXT("Reading m_HookSettingEntryArray failed\n"));
		return FALSE;
	}

	return TRUE;
}


BOOL HookSettingReader::StartHook()
{
	assert( m_dwHookSettingEntryCount<=MaxHookSettingEntryCount );

	HookEngine::SuspendAllThreads();
	for(DWORD dwHookAPIIndex=0;dwHookAPIIndex<m_dwHookSettingEntryCount;dwHookAPIIndex++)
	{
		BOOL fStartHookResult = m_pHookEngine->Start(&(m_HookSettingEntryArray[dwHookAPIIndex]));
		assert( fStartHookResult );
		if( !fStartHookResult )
		{
			TRACE(TEXT("HookEngine::Start fails!\n"));
			return FALSE;
		}
	}
	HookEngine::ResumeAllThreads();

	return TRUE;
}

void HookSettingReader::StopHook()
{
	assert( m_dwHookSettingEntryCount<= MaxHookSettingEntryCount );

	HookEngine::SuspendAllThreads();
	for(DWORD dwHookAPIIndex=0;dwHookAPIIndex<m_dwHookSettingEntryCount;dwHookAPIIndex++)
	{
		BOOL HookEngineStopResult = m_pHookEngine->Stop(&(m_HookSettingEntryArray[dwHookAPIIndex]));
		//assert( HookEngineStopResult );
	}
	HookEngine::ResumeAllThreads();
}


